package cn.ddiancan.auth.controller;

import java.util.Objects;

import cn.ddiancan.xddcloud.common.constants.XddHeaderConstant;
import cn.ddiancan.xddcloud.common.entity.CommonResult;
import cn.ddiancan.xddcloud.common.entity.UserVO;
import cn.ddiancan.xddcloud.ddccore.cache.XddCloudCacheClient;
import com.alibaba.fastjson.JSON;
import jakarta.servlet.http.HttpServletRequest;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.oauth2.jwt.Jwt;
import org.springframework.security.oauth2.server.authorization.OAuth2Authorization;
import org.springframework.security.oauth2.server.authorization.OAuth2AuthorizationService;
import org.springframework.security.oauth2.server.authorization.OAuth2TokenType;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@Slf4j
@RestController
@RequestMapping("/token")
public class XddCloudTokenController {

    private static final String ACCESS_TOKEN = "x-access-token";

    private final static String USER_KEY = XddHeaderConstant.PERMISSION_CACHE_PREFIX;

    private static final String LOGIN_TYPE = "loginType";

    private final static String SPER = "_";

    @Autowired
    @Lazy
    private OAuth2AuthorizationService oAuth2AuthorizationService;

    @Autowired
    private XddCloudCacheClient xddCloudCacheClient;

    @GetMapping("/validate")
    public CommonResult<UserVO> getToken(HttpServletRequest request) {
        try {
            String resolveToken = request.getHeader(ACCESS_TOKEN);
            if (StringUtils.hasText(resolveToken)) {
                return getUserByAccessToken();
            }
        } catch (Exception e) {
            log.error(e.getMessage(), e);
        }
        return CommonResult.failed("无效凭证，认证失败");
    }

    private CommonResult<UserVO> getUserByAccessToken() {
        try {
            // 上下文中获取认证信息
            Authentication authenticationResult = SecurityContextHolder.getContext().getAuthentication();
            Jwt principal = (Jwt) authenticationResult.getPrincipal();
            String content = (String) principal.getClaims().get("content");
            UserVO userResult = JSON.parseObject(content, UserVO.class);
            userResult.setPassword(null);
            userResult.setInitPassword(null);
            return CommonResult.success(userResult);
        } catch (Exception e) {
            log.error(e.getMessage(), e);
        }
        return CommonResult.failed();
    }

    @GetMapping("/logout")
    public CommonResult<?> logoutToken(HttpServletRequest request) {
        log.info("打印sessionId:{}", request.getSession().getId());
        // 清除认证信息
        String resolveToken = request.getHeader(ACCESS_TOKEN);
        OAuth2Authorization byToken =
            oAuth2AuthorizationService.findByToken(resolveToken, OAuth2TokenType.ACCESS_TOKEN);
        if (Objects.nonNull(byToken)) {
            oAuth2AuthorizationService.remove(byToken);
            xddCloudCacheClient.deleteByKey(USER_KEY.concat(byToken.getPrincipalName()));
            String requestType = byToken.getAttribute(LOGIN_TYPE);
            if (StringUtils.hasText(requestType)) {
                xddCloudCacheClient.deleteByKey(
                    USER_KEY.concat(requestType).concat(SPER).concat(byToken.getPrincipalName()));
            }

        }
        return CommonResult.success();
    }
}
